home *** CD-ROM | disk | FTP | other *** search
/ Atari Mega Archive 1 / Atari Mega Archive - Volume 1.iso / gnu / bash / bash_110 / mint / bash110s.zoo / bash-1.10 / copy_cmd.c < prev    next >
Encoding:
C/C++ Source or Header  |  1991-09-03  |  7.1 KB  |  278 lines

  1. /* copy_command.c -- copy a COMMAND structure.  This is needed
  2.    primarily for making function definitions, but I'm not sure
  3.    that anyone else will need it.  */
  4.  
  5. /* Copyright (C) 1987,1991 Free Software Foundation, Inc.
  6.  
  7.    This file is part of GNU Bash, the Bourne Again SHell.
  8.  
  9.    Bash is free software; you can redistribute it and/or modify it
  10.    under the terms of the GNU General Public License as published by
  11.    the Free Software Foundation; either version 1, or (at your option)
  12.    any later version.
  13.  
  14.    Bash is distributed in the hope that it will be useful, but WITHOUT
  15.    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
  16.    or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public
  17.    License for more details.
  18.  
  19.    You should have received a copy of the GNU General Public License
  20.    along with Bash; see the file COPYING.  If not, write to the Free
  21.    Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
  22.  
  23. #include <stdio.h>
  24. #include "shell.h"
  25.  
  26. /* Forward declaration. */
  27. extern COMMAND *copy_command ();
  28.  
  29. WORD_DESC *
  30. copy_word (word)
  31.      WORD_DESC *word;
  32. {
  33.   WORD_DESC *new_word = (WORD_DESC *)xmalloc (sizeof (WORD_DESC));
  34.   bcopy (word, new_word, sizeof (WORD_DESC));
  35.   new_word->word = savestring (word->word);
  36.   return (new_word);
  37. }
  38.  
  39. /* Copy the chain of words in LIST.  Return a pointer to 
  40.    the new chain. */
  41. WORD_LIST *
  42. copy_word_list (list)
  43.      WORD_LIST *list;
  44. {
  45.   WORD_LIST *new_list = NULL;
  46.  
  47.   while (list)
  48.     {
  49.       WORD_LIST *temp = (WORD_LIST *)xmalloc (sizeof (WORD_LIST));
  50.       temp->next = new_list;
  51.       new_list = temp;
  52.       new_list->word = copy_word (list->word);
  53.       list = list->next;
  54.     }
  55.   return ((WORD_LIST *)reverse_list (new_list));
  56. }
  57.  
  58. PATTERN_LIST *
  59. copy_case_clause (clause)
  60.      PATTERN_LIST *clause;
  61. {
  62.   PATTERN_LIST *new_clause = (PATTERN_LIST *)xmalloc (sizeof (PATTERN_LIST));
  63.   new_clause->patterns = copy_word_list (clause->patterns);
  64.   new_clause->action = copy_command (clause->action);
  65.   return (new_clause);
  66. }
  67.  
  68. PATTERN_LIST *
  69. copy_case_clauses (clauses)
  70.      PATTERN_LIST *clauses;
  71. {
  72.   PATTERN_LIST *new_list = (PATTERN_LIST *)NULL;
  73.  
  74.   while (clauses)
  75.     {
  76.       PATTERN_LIST *new_clause = copy_case_clause (clauses);
  77.       new_clause->next = new_list;
  78.       new_list = new_clause;
  79.       clauses = clauses->next;
  80.     }
  81.   return ((PATTERN_LIST *)reverse_list (new_list));
  82. }
  83.  
  84. /* Copy a single redirect. */
  85. REDIRECT *
  86. copy_redirect (redirect)
  87.      REDIRECT *redirect;
  88. {
  89.   REDIRECT *new_redirect = (REDIRECT *)xmalloc (sizeof (REDIRECT));
  90.   bcopy (redirect, new_redirect, (sizeof (REDIRECT)));
  91.   switch (redirect->instruction)
  92.     {
  93.     case r_reading_until:
  94.     case r_deblank_reading_until:
  95.       new_redirect->here_doc_eof = savestring (redirect->here_doc_eof);
  96.       /* There is NO BREAK HERE ON PURPOSE!!!! */
  97.     case r_appending_to:
  98.     case r_output_direction:
  99.     case r_input_direction:
  100.     case r_inputa_direction:
  101.     case r_err_and_out:
  102.     case r_input_output:
  103.     case r_output_force:
  104.       new_redirect->redirectee.filename =
  105.     copy_word (redirect->redirectee.filename);
  106.       break;
  107.     }
  108.   return (new_redirect);
  109. }
  110.   
  111. REDIRECT *
  112. copy_redirects (list)
  113.      REDIRECT *list;
  114. {
  115.   REDIRECT *new_list = NULL;
  116.  
  117.   while (list)
  118.     {
  119.       REDIRECT *temp = copy_redirect (list);
  120.       temp->next = new_list;
  121.       new_list = temp;
  122.       list = list->next;
  123.     }
  124.   return ((REDIRECT *)reverse_list (new_list));
  125. }
  126.   
  127. FOR_COM *
  128. copy_for_command (com)
  129.      FOR_COM *com;
  130. {
  131.   FOR_COM *new_for = (FOR_COM *)xmalloc (sizeof (FOR_COM));
  132.   new_for->flags = com->flags;
  133.   new_for->name = copy_word (com->name);
  134.   new_for->map_list = copy_word_list (com->map_list);
  135.   new_for->action = copy_command (com->action);
  136.   return (new_for);
  137. }
  138.  
  139. GROUP_COM *
  140. copy_group_command (com)
  141.      GROUP_COM *com;
  142. {
  143.   GROUP_COM *new_group = (GROUP_COM *)xmalloc (sizeof (GROUP_COM));
  144.  
  145.   new_group->command = copy_command (com->command);
  146.   return (new_group);
  147. }
  148.  
  149. CASE_COM *
  150. copy_case_command (com)
  151.      CASE_COM *com;
  152. {
  153.   CASE_COM *new_case = (CASE_COM *)xmalloc (sizeof (CASE_COM));
  154.  
  155.   new_case->flags = com->flags;
  156.   new_case->word = copy_word (com->word);
  157.   new_case->clauses = copy_case_clauses (com->clauses);
  158.   return (new_case);
  159. }
  160.  
  161. WHILE_COM *
  162. copy_while_command (com)
  163.      WHILE_COM *com;
  164. {
  165.   WHILE_COM *new_while = (WHILE_COM *)xmalloc (sizeof (WHILE_COM));
  166.  
  167.   new_while->flags = com->flags;
  168.   new_while->test = copy_command (com->test);
  169.   new_while->action = copy_command (com->action);
  170.   return (new_while);
  171. }
  172.  
  173. IF_COM *
  174. copy_if_command (com)
  175.      IF_COM *com;
  176. {
  177.   IF_COM *new_if = (IF_COM *)xmalloc (sizeof (IF_COM));
  178.  
  179.   new_if->flags = com->flags;
  180.   new_if->test = copy_command (com->test);
  181.   new_if->true_case = copy_command (com->true_case);
  182.   new_if->false_case = copy_command (com->false_case);
  183.   return (new_if);
  184. }
  185.  
  186. SIMPLE_COM *
  187. copy_simple_command (com)
  188.      SIMPLE_COM *com;
  189. {
  190.   SIMPLE_COM *new_simple = (SIMPLE_COM *)xmalloc (sizeof (SIMPLE_COM));
  191.  
  192.   new_simple->flags = com->flags;
  193.   new_simple->words = copy_word_list (com->words);
  194.   new_simple->redirects = copy_redirects (com->redirects);
  195.   return (new_simple);
  196. }
  197.   
  198. FUNCTION_DEF *
  199. copy_function_def (com)
  200.      FUNCTION_DEF *com;
  201. {
  202.   FUNCTION_DEF *new_def = (FUNCTION_DEF *)xmalloc (sizeof (FUNCTION_DEF));
  203.  
  204.   new_def->name = copy_word (com->name);
  205.   new_def->command = copy_command (com->command);
  206.   return (new_def);
  207. }
  208.  
  209. /* Copy the command structure in COMMAND.  Return a pointer to the
  210.    copy.  Don't you forget to dispose_command () on this pointer
  211.    later! */
  212. COMMAND *
  213. copy_command (command)
  214.      COMMAND *command;
  215. {
  216.   COMMAND *new_command = (COMMAND *)NULL;
  217.  
  218.   if (command)
  219.     {
  220.       new_command = (COMMAND *)xmalloc (sizeof (COMMAND));
  221.       bcopy (command, new_command, sizeof (COMMAND));
  222.       new_command->flags = command->flags;
  223.  
  224.       if (command->redirects)
  225.     new_command->redirects = copy_redirects (command->redirects);
  226.  
  227.       switch (command->type)
  228.     {
  229.     case cm_for:
  230.       new_command->value.For = copy_for_command (command->value.For);
  231.       break;
  232.  
  233.     case cm_group:
  234.       new_command->value.Group = copy_group_command (command->value.Group);
  235.       break;
  236.  
  237.     case cm_case:
  238.       new_command->value.Case = copy_case_command (command->value.Case);
  239.       break;
  240.       
  241.     case cm_until:
  242.     case cm_while:
  243.       new_command->value.While = copy_while_command (command->value.While);
  244.       break;
  245.       
  246.     case cm_if:
  247.       new_command->value.If = copy_if_command (command->value.If);
  248.       break;
  249.       
  250.     case cm_simple:
  251.       new_command->value.Simple = copy_simple_command (command->value.Simple);
  252.       break;
  253.       
  254.     case cm_connection:
  255.       {
  256.         CONNECTION *new_connection;
  257.  
  258.         new_connection = (CONNECTION *)xmalloc (sizeof (CONNECTION));
  259.         new_connection->connector = command->value.Connection->connector;
  260.         new_connection->first =
  261.           copy_command (command->value.Connection->first);
  262.         new_connection->second =
  263.           copy_command (command->value.Connection->second);
  264.         new_command->value.Connection = new_connection;
  265.         break;
  266.       }
  267.       
  268.       /* Pathological case.  I'm not even sure that you can have a
  269.          function definition as part of a function definition. */
  270.     case cm_function_def:
  271.       new_command->value.Function_def =
  272.         copy_function_def (command->value.Function_def);
  273.       break;
  274.     }
  275.     }
  276.   return (new_command);
  277. }
  278.